/*
 * List.c
 *
 *  Created on: 2011-3-15
 *      Author: william nie
 */

#include "List.h"

Status InitList(List **listP){

	printf("初始化线性表。\n");
	*listP = (List*)malloc(sizeof(List));

	(*listP)->elem = (LElemType*) malloc(LIST_INIT_SIZE * sizeof(LElemType));

	if(!(*listP)){
		exit(OVERFLOW);
	}

	(*listP)->length = 0;
	(*listP)->listsize = LIST_INIT_SIZE;

	printf("初始化线性表完毕。\n\n");
	return OK;
}

Status DestoryList(List **list){
	printf("销毁表。\n");

	LElemType *elems = (*list)->elem;

	free(elems);
	free(*list);
	*list = NULL;

	printf("销毁表完毕。\n");

	return OK;
}

Status ClearList(List *list){
	printf("清空表。\n");

	list->length=0;

	printf("清空表完毕。\n\n");

	return OK;
}

BOOL ListEmpty(List *list){
	if(list->length==0){
		return FALSE;
	}else{
		return TRUE;
	}
}

int ListLength(List *list){
	return list->length;
}

LElemType GetElem(List *list , int loc){
	printf("获得d%处的元素。\n",loc);

	LElemType *elems = list->elem;

	printf("获得元素完毕。\n\n");

	return *(elems + loc - 1);
}

int LocateElem(List *list , LElemType elemToCompare){
	printf("获得元素%d在链表中的位置。\n" , elemToCompare);

	LElemType *elems = list->elem;
	int locate = 0;

	while(!DefaultCompare(elemToCompare,*(elems + locate))){
		++locate;
	}

	printf("获得位置完毕。\n\n");

	return locate + 1;
}

LElemType PriorElem(List *list , LElemType elem){
	printf("获得元素%d的直接前驱元素。\n",elem);

	LElemType *elems = list->elem;
	int count = 0;

	while(*(elems + count)!=elem){
		++count;
	}

	if(count==0||count==list->length){
		exit(ERROR);
	}

	printf("获得前驱完毕。\n\n");

	return *(elems + count -1);
}

LElemType NextElem(List *list , LElemType elem){
	printf("获得元素%d的直接后继元素。\n",elem);

	LElemType *elems = list->elem;
	int count = 0;

	while(*(elems + count) != elem){
		++count;
	}

	if(count==list->length-1||count==list->length){
		exit(ERROR);
	}

	printf("获得后继元素完毕。\n\n");

	return *(elems + count + 1);
}

Status ListInsert(List *list , int loc , LElemType elem){
	printf("在%d位置插入元素%d。\n",loc + 1,elem);

	if(loc<0||loc>=list->length){
		exit(ERROR);
	}

	if(list->length==list->listsize){
		list->elem=(LElemType*)realloc(list->elem,list->listsize + LIST_INCREMENT);
		list->listsize+=LIST_INCREMENT;
	}

	LElemType *elems = list->elem;
	int count = list->length;

	do{
		*(elems+count) = *(elems+count-1);
		--count;
	}while(count!=loc);

	*(elems+loc)=elem;

	list->length+=1;

	printf("插入元素完毕。\n\n");

	return OK;
}

LElemType ListDelete(List *list , int loc ){
	printf("删除位置为%d的元素。\n",loc + 1);

	if(loc<0||loc>=list->length){
		exit(ERROR);
	}

	LElemType *elems = list->elem;
	int count = loc;
	while(count<list->length){
		*(elems+count)=*(elems+count+1);
		++count;
	}
	list->length-=1;

	printf("删除元素完毕。\n");

	return OK;
}

BOOL ListTraverse(List *list , Visit visit){
	printf("遍历并访问链表。\n");

	LElemType *elems = list->elem;
	int listLength = list->length;
	int count = 0;

	for(; count < listLength ; ++count){
		if(visit(*(elems + count))){
			continue;
		} else {
			return FALSE;
		}
	}

	printf("\n");
	printf("遍历并访问完毕。\n\n");

	return TRUE;
}

Status FillList(List *list){
	int counter = 0;
	LElemType *elems;

	printf("填充链表。\n");

	if(list->length==0){
		printf("开始填充表。\n");
		printf("填充表长：\n");
		scanf("%d",&list->length);
		if(list->length>list->listsize){
			list->elem=(LElemType*)realloc(list->elem,list->length*sizeof(LElemType));
			list->listsize=list->length*sizeof(LElemType);
		}
	}

	elems = list->elem;

	printf("当前表长为%d。\n",list->length);

	printf("现在请填写表中元素：\n");

	for(;counter<list->length;counter++){
		scanf("%d",elems + counter);
	}

	printf("填充表完毕。\n\n");

	return OK;
}

Status PrintList(List *list){
	int length = list->length;
	int listSize = list->listsize;
	LElemType *elems = list->elem;
	int counter = 0;

	if(length==0){
		printf("表为空。\n");
		return ERROR;
	}else{
		printf("表长为%d。\n",length);
	}

	printf("表所占内存大小为%d。\n",listSize);
	printf("表元素为：\n");

	for(;counter<length;counter++){
		printf("%d ",*(elems+counter));
	}
	printf("\n\n");

	return OK;
}

Status PrintListElem(List *list){
	if(list->length==0){
		printf("表为空。\n\n");
		return ERROR;
	}

	LElemType *elems = list->elem;
	int counter = 0;
	printf("表元素为：\n");
	for(;counter<list->length;counter++){
		printf("%d ",*(elems+counter));
	}

	printf("\n\n");

	return OK;
}

BOOL DefaultCompare(LElemType elem1 , LElemType elem2){
	if(elem1==elem2){
		return TRUE;
	} else {
		return FALSE;
	}
}

BOOL DefaultVisit(LElemType elem){
	printf("%d " , elem);
	return TRUE;
}
